import httplib
import urllib
import urlparse
    

class Connection( httplib.HTTPConnection ):
    
    def __init__( self, method, uri, data=None, header=None ):
        
        try: 
            uri = urlparse.urlparse(uri); 
        except AttributeError: 
            raise Exception, 'Error parsing uri'
        else:
            path   = uri[2]
            query  = uri[4]
            host   = uri[1]
        
        httplib.HTTPConnection.__init__( self, host )

        self.connect()
        
        self.path   = urllib.quote( urllib.unquote(path.encode('utf-8')), safe='/;' )
        self.uri    = uri
        self.query  = query
        self.method = method
        self.data   = data
        self.header = header
        self.host   = host
        
        
        
    def send_request( self ):
        query = '%s%s' % (self.path, ('','?%s' % self.query)[len(self.query) > 0] ) 
        
        print '%s send request :: %s %s%s' % ( self.__class__.__name__, self.method, self.host, query )
        
        try:
            self.putrequest(self.method, query)
            
            if self.header: 
                for key in self.header: self.putheader(key, self.header[key])
            self.endheaders()   
            self.send(self.data or '')
        except:
            return None
        else:
            return True
            

          

    def get_response( self ):       
        response = self.getresponse()
        print '%s return code: %d' % (repr('%s?%s' % (self.path, self.query)), response.status)
            
        if response.status not in range(200,300):
            if response.status == 301:
                location = response.getheader('location', None)
                if location == None: return None
                sub_conn = HTTP( self.method, urllib.unquote(location), self.data, self.header )
                response = sub_conn.response()
                subb_conn.close()
            else:
                return None
        else: return response
     
     
     
    def response( self ):
        if self.send_request():
            return self.get_response()    
            
            
    def destroy( self ):
        self.close()          
                   
      
      
               
               
def method_get( uri, header=None ):
    conn = Connection( 'GET', uri, header=header )  
    if not conn.path: conn.path = '/'        
    conn.query = urllib.quote(urllib.unquote(conn.query.encode('utf-8')), safe='=&?/')
    
    data = str()
    data_head = tuple()
    response = conn.response()
    if response:
        data_head = response.getheaders()
        data = response.read()
    conn.destroy()
    
    return data_head, data
    
        
        
def method_post( uri, data=None, header=None ):
    conn = Connection( 'POST', uri, data, header )  
    if not conn.path: conn.path = '/'        

    data = str()
    data_head = tuple()
    response = conn.response()
    if response:
        data_head = response.getheaders()
        data = response.read()
    conn.destroy()
    
    return data_head, data
    
    
    
def method_head( uri, header=None ):
    conn = Connection( 'HEAD', uri, header=header )  
    if not conn.path: conn.path = '/'        

    data_header = str()
    response = conn.response()
    if response:
        data_header = response.getheaders()
    conn.destroy()
    
    return data_headers, ''
    
     



def get_mime_type(data_head):
    for entry in data_head:
        if entry[0] == 'content-type':
            return entry[1]
    
    
            

def open( uri, callback=None, id=None ):
    if uri.startswith( 'http://' ):
        method_get( uri, callback=callback, id=id )
    elif uri.startwith( 'mms://' ):
        method_get( uri.replace('mms://', 'http://'), callback=callback, id=id )
        
